import React, {
  Component,
  createRef,
  createContext,
  useRef,
  useState,
  useEffect,
} from "react";
import PropType from "prop-types";
import "./Home.css";
import { BrowserRouter as Router, Routes, Route } from "react-router-dom";
import * as THREE from "three";
import { OrbitControls } from "three/examples/jsm/controls/OrbitControls";
import gsap from "gsap"; //动画库
import Stats from "stats.js"; //性能监控
import { FBXLoader } from "three/examples/jsm/loaders/FBXLoader.js"; // FBX 模型加载器
import { GLTFLoader } from "three/examples/jsm/loaders/GLTFLoader"; //模型加载器
import { DRACOLoader } from "three/examples/jsm/loaders/DRACOLoader"; //模型解压缩

import { RGBELoader } from "three/examples/jsm/loaders/RGBELoader"; //模型加载器
import { Lut } from "three/examples/jsm/math/Lut.js";
const width = window.innerWidth;
const height = window.innerHeight;
const scene = new THREE.Scene();
scene.background = new THREE.Color(0xffffff);

const uiScene = new THREE.Scene();
const lut = new Lut();

const renderer = new THREE.WebGLRenderer({ antialias: true });

const camera = new THREE.PerspectiveCamera(60, width / height, 1, 100);

camera.position.set(0, 0, 10);
scene.add(camera);


const orthoCamera = new THREE.OrthographicCamera(-1, 1, 1, -1, 1, 2);
orthoCamera.position.set(0.5, 0, 1);

const controls = new OrbitControls(camera, renderer.domElement);

const sprite = new THREE.Sprite( //精灵是一个总是面朝着摄像机的平面，通常含有使用一个半透明的纹理。精灵不会投射任何阴影，即使设置了
  new THREE.SpriteMaterial({ //一种使用Sprite的材质。(点精灵材质)
    //.map : Texture
    //颜色贴图。可以选择包括一个alpha通道，通常与.transparent 或.alphaTest。默认为null。
    map: new THREE.CanvasTexture( //从Canvas元素中创建纹理贴图。它几乎与其基类Texture相同，但它直接将needsUpdate（需要更新）设置为了true。
      lut.createCanvas() // 创建画布，以便将查找表可视化为纹理。
      ),
  })
);
uiScene.add(sprite);

const mesh = new THREE.Mesh( //表示基于以三角形为polygon mesh（多边形网格）的物体的类。 同时也作为其他类的基类，例如SkinnedMesh。
  undefined,
  new THREE.MeshLambertMaterial({ //一种非光泽表面的材质，没有镜面高光。
    side: THREE.DoubleSide, //双面 渲染
    color: 0xf5f5f5,
    vertexColors: true, //是否使用顶点着色。默认值为false。
  })
);
scene.add(mesh);

const pointLight = new THREE.PointLight(0xffffff, 1); //点光源
camera.add(pointLight);

const ReactDemo = () => {
  useEffect(() => {
    init();
    animate();
  }, []);
  function init() {
    const container = document.createElement("div");
    document.body.appendChild(container);
    const loader = new THREE.BufferGeometryLoader(); //用来加载BufferGeometry的加载器。 内部使用FileLoader来加载文件。
    loader.load("./3D/pressure.json", function (geometry) {
      geometry.center(); //根据边界矩形将几何体居中。

   
     geometry.computeVertexNormals(); //通过面片法向量的平均值计算每个顶点的法向量。
      console.log( geometry.attributes.position,'11')
      // default color attribute
      const colors = [];

      for (let i = 0, n = geometry.attributes.position.count; i < n; ++i) {
        colors.push(1, 1, 1);
      }

      geometry.setAttribute(
        "color",
        new THREE.Float32BufferAttribute(colors, 3)
      );

      mesh.geometry = geometry;
      updateColors();

      // render();
    });
    renderer.autoClear = false; //定义渲染器是否在渲染每一帧之前自动清除其输出。
    renderer.setPixelRatio(window.devicePixelRatio); //设置设备像素比。通常用于避免HiDPI设备上绘图模糊
    renderer.setSize(width, height); // canvas 大小设置
    renderer.toneMapping = THREE.ACESFilmicToneMapping; //这些常量定义了WebGLRenderer中toneMapping的属性。 这个属性用于在普通计算机显示器或者移动设备屏幕等低动态范围介质上，模拟、逼近高动态范围（HDR）效果。
    renderer.toneMappingExposure = 0.8; //色调映射的曝光级别。默认是1
    renderer.outputEncoding = THREE.sRGBEncoding; //定义渲染器的输出编码
    container.appendChild(renderer.domElement); // 把canvas 添加到 到div 中

    window.addEventListener("resize", onWindowResize);
  }

  function onWindowResize() {
    camera.aspect = window.innerWidth / window.innerHeight;
    camera.updateProjectionMatrix();

    renderer.setSize(width, height);
  }
  const color1 = new THREE.Color(0x0000ff); //山谷颜色
  const color2 = new THREE.Color(0x00ff00); //山腰颜色
  const color3 = new THREE.Color(0xff0000); //山顶颜色
  function updateColors() {
   
    lut.setMax(2000); // maxV-要用查找表表示的最大值。将此Lut设置为要表示的最大值。
    lut.setMin(0); //minV-用查找表表示的最小值。将此Lut设置为要表示的最小值。

    
    console.log(lut.lut,'lut')
console.log(lut.map,'map')
console.log(lut.minV,'minV',lut.maxV,lut.n)
    const geometry = mesh.geometry;
    const pressures: any = geometry.attributes.pressure;
    const colors: any = geometry.attributes.color;
//  console.log(colors,'colorscolors')
    for (let i = 0; i < pressures.array.length; i++) {
      const colorValue = pressures.array[i];

      const color = lut.getColor(colorValue);  //value——要显示为颜色的数据值。返回给定数据值的Color实例。
    //  console.log(color,'colorcolor 获取到数据',colorValue)

      if (color === undefined) {
        console.log("Unable to determine color for value:", colorValue);
      } else {
      //  colors.setXYZ(i, color.r, color.g, color.b); //设置给定索引的矢量的第一、二、三维数据（设置 X、Y 和 Z 值）。
      // console.log(color1.clone().lerp(color2, i),'1111111111')
        if(colorValue<1680 &&colorValue>1655){
          // colors.setXYZ(i, color.r, color.g, color.b); //设置给定索引的矢量的第一、二、三维数据（设置 X、Y 和 Z 值）。
           colors.setXYZ(i,color1.clone().lerp(color3,0.8).r, color1.clone().lerp(color3, 0.8).g, color1.clone().lerp(color3, 0.8).b); 
        }
        // colors.setXYZ(i,1, 0, 0); //设置给定索引的矢量的第一、二、三维数据（设置 X、Y 和 Z 值）。
      }
    }

    colors.needsUpdate = true; //默认值为true，这是必须的，以便使得Canvas中的数据能够载入。

    const map: any = sprite.material.map;
    lut.updateCanvas(map.image); //使用Lut的数据更新画布。
    map.needsUpdate = true;//默认值为true，这是必须的，以便使得Canvas中的数据能够载入。
  }

  function animate() {
    requestAnimationFrame(animate);

    renderer.render(scene, camera);

    controls.update();
  }
  return <></>;
};

export default ReactDemo;
